package view;

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Image;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Vector;
import javax.imageio.ImageIO;
import javax.swing.JFrame;
import javax.swing.JPanel;
import model.*;

public class Grid extends JPanel{
	
	int nbRows;
	int nbColumns;
	Space2D universe;
	
	int rowStep;
	int columnStep;
	boolean isPheromoneActivated;
	boolean isTracesActivated;
	
	public Grid(Space2D universe, boolean isPheromoneActivated){
		super();
		this.universe = universe;
		this.nbRows = universe.getDimX();
		this.nbColumns = universe.getDimY();
		this.isPheromoneActivated = isPheromoneActivated;
		
		this.rowStep = 16;
		this.columnStep = 16;
	}
	
	public void paintComponent(Graphics g){
		
		//int auxColumn = this.getWidth()/this.nbColumns;
		//this.columnStep = auxColumn - auxColumn%4;
		
		//int auxRow = this.getHeight()/this.nbRows;
		//this.rowStep = auxRow - auxRow%4;
		
		g.setColor(Color.WHITE);
		g.fillRect(0, 0, this.getWidth(), this.getHeight());
		
		// Paint the cells
		this.paintCells(g);
		
		// Paint the grid
		g.setColor(Color.BLACK);
		this.paintGrid(g);
		
		//Paint the traces
		if (this.isTracesActivated){
			this.paintTraces(g);
		}
	}
	
	// Paint the grid
	public void paintGrid(Graphics g){
		
		// Draw the rows
		for (int i = 0; i<nbRows+1; i++){
			g.drawLine(0, i*(this.rowStep+1), this.nbColumns*(this.columnStep+1), i*(this.rowStep+1));		
		}
		
		// Draw the columns
		for (int i = 0; i<nbColumns+1; i++){
			g.drawLine(i*(this.columnStep+1), 0, i*(this.columnStep+1), this.nbRows*(this.rowStep+1));
		}
	}
	
	// Paint the cells
	public void paintCells(Graphics g){
		
		for (int i=0; i<this.universe.getDimX(); i++){
			for (int j=0; j<this.universe.getDimY(); j++){
				Point p = new Point(i, j);
				Cell cell = this.universe.getCell(p);
				if (cell != null){
					this.paintCell(g, p, cell);
				}
			}
		}
		
	}
	
	// Paint a cell
	public void paintCell(Graphics g, Point p, Cell cell){
		
		int x = (columnStep+1)*p.getY();
		
		int y = (rowStep+1)*p.getX();
		
		//Paint the pheromone
		if (this.isPheromoneActivated){
			int pheromone = cell.getPheromone();
			if (pheromone > 0){
				g.setColor(new Color((new Double(255-pheromone*1.8)).intValue(),(new Double(255-pheromone*1.8)).intValue(),(new Double(255-pheromone*1.8)).intValue()));
				g.fillRect(x+1, y+1, columnStep, rowStep);
			}
		}
		//Paint the Resource
		Resource resource = cell.getResource();
		if (resource != null){
			String type = resource.getType();
			if (type.equalsIgnoreCase("r1")){
				g.setColor(Color.red);
				g.fillRect(x+columnStep/4+1, y+rowStep/4+1, columnStep/2, rowStep/2);
			} else if (type.equalsIgnoreCase("r2")){
				g.setColor(Color.blue);
				g.fillOval(x+columnStep/4+1, y+rowStep/4+1, columnStep/2, rowStep/2);
			} else if (type.equalsIgnoreCase("r3")){
				g.setColor(Color.green);
				int[] xpoints = {x+columnStep/2+1, x+columnStep/2+2, x+columnStep/4+1, x+3*columnStep/4+1};
				int[] ypoints = {y+rowStep/4+1, y+rowStep/4+1, y+3*rowStep/4+1, y+3*rowStep/4+1};
				g.fillPolygon(xpoints, ypoints, 4);
			}
		}
		
		//Paint the ant
		Ant ant = cell.getAnt();
		if (ant != null){
			try {
				//Image img = ImageIO.read(new File("/image/ant.gif"));
				Image img = ImageIO.read(getClass().getResource("/image/ant.gif"));
				g.drawImage(img, x, y, columnStep, rowStep, this);
				
				if (this.isTracesActivated){
					Vector<Point> v = ant.getHistMoves();
					Point origin = v.get(0);
					int xOrigin = (columnStep+1)*origin.getY();
					int yOrigin = (rowStep+1)*origin.getX();
					g.setColor(Color.BLACK);
					g.drawRect(xOrigin+1, yOrigin+1, columnStep-1, rowStep-1);
					g.drawRect(xOrigin-1, yOrigin-1, columnStep+3, rowStep+3);
					g.setColor(Color.MAGENTA);
					for (int i = 0; i<v.size()-1;i++){
						Point point = v.get(i);
						Point point2 = v.get(i+1);
						int pointX = (columnStep+1)*point.getY();
						int pointY = (rowStep+1)*point.getX();
						int point2X = (columnStep+1)*point2.getY();
						int point2Y = (rowStep+1)*point2.getX();

						g.drawLine(pointX+columnStep/2, pointY+rowStep/2, point2X+columnStep/2, point2Y+rowStep/2);

					}
				}
				
			} catch (IOException e) {
				e.printStackTrace();
			}
		}	
	}
	
	public static void main(String[] args) throws Exception{
		JFrame frame = new JFrame("Test");
		
		Space2D universe = new Space2D(30, 30);
		Point p1 = new Point(0,0);
		Point p2 = new Point(7,3);
		Point p3 = new Point(4,5);
		Point p4 = new Point(7,9);
		
		Point p5 = new Point(2,2);
		
		Ant ant1 = new Ant(universe, p5, 0, 0, "None");
		Ant ant2 = new Ant(universe, p2, 0, 0, "None");
		Resource r1 = new Resource(universe, p1, "r1");
		Resource r2 = new Resource(universe, p3, "r2");
		Resource r3 = new Resource(universe, p4, "r3");
		
		universe.addAnt(ant1);
		universe.addAnt(ant2);
		universe.addResource(r1);
		universe.addResource(r2);
		universe.addResource(r3);
		
		Grid grid = new Grid(universe, false);
		
		frame.setSize(500, 500);
		frame.setLocationRelativeTo(null);               
		frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		
		frame.add(grid);
		
		frame.setVisible(true);
		
		while(true){
			ant1.step();
			grid.repaint();
			Thread.sleep(10);
		}
		
	}

	void setPheromoneActivated(boolean b) {
		this.isPheromoneActivated = b;
	}

	void setTracesActivated(boolean tracesActivated) {
		this.isTracesActivated = tracesActivated;
	}

	private void paintTraces(Graphics g) {
		
		ArrayList<Ant> listAnts = this.universe.getListAnts();
		
		for (int j = 0; j<listAnts.size();j++){
			Ant ant = listAnts.get(j);
					Vector<Point> v = ant.getHistMoves();
					Point origin = v.get(0);
					int xOrigin = (columnStep+1)*origin.getY();
					int yOrigin = (rowStep+1)*origin.getX();
					g.setColor(Color.ORANGE);
					g.drawRect(xOrigin+1, yOrigin+1, columnStep-1, rowStep-1);
					g.drawRect(xOrigin-1, yOrigin-1, columnStep+3, rowStep+3);
					g.setColor(Color.MAGENTA);
					for (int i = 0; i<v.size()-1;i++){
						Point point = v.get(i);
						Point point2 = v.get(i+1);
						int pointX = (columnStep+1)*point.getY();
						int pointY = (rowStep+1)*point.getX();
						int point2X = (columnStep+1)*point2.getY();
						int point2Y = (rowStep+1)*point2.getX();

						g.drawLine(pointX+columnStep/2, pointY+rowStep/2, point2X+columnStep/2, point2Y+rowStep/2);

					}
				}
				
			}

}
